package main;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayDeque;
import java.util.Deque;
import java.util.HashSet;
import java.util.Observable;
import java.util.Observer;
import java.util.Set;
import java.util.TreeSet;

public class PageRetriever extends Observable {
	private Set<String> myVisitedPages;
	private Deque<URL> myPagesToVisit;
	private int totalPages;
//	private Deque<String> myPageRepository; //multi-threaded
	
	
	public PageRetriever() {
		myVisitedPages = new HashSet<String>(); //might need to change this...
		myPagesToVisit = new ArrayDeque<URL>();
	}
	
	public boolean addPage(final String theURLString) {
		boolean success = true;
		System.out.println("I'm in the PR addPage method");
		URL theURL;
		try {
			theURL = new URL(theURLString);
			System.out.println(validateURL(theURL));
//			if (!myVisitedPages.contains(theURL)) {
			if (myVisitedPages.size() < totalPages) {
				if (validateURL(theURL) == true && myVisitedPages.add(theURL.toString()) == true) {
					myPagesToVisit.add(theURL); //adding to rear
					System.out.println("PR added: " + myPagesToVisit.peekLast().toString()); //checking what I added
				} else {
					System.out.println(theURL.toString() + " not added because it is not valid, or has already been parsed..............");
				}
			}
		} catch (MalformedURLException e) {
			// TODO Auto-generated catch block
			System.out.println(theURLString + " is not a valid URL. Exiting");
			success = false;
		}
		return success;
	}
	
	/**
	 * Need to figure out what to do with URLs with no .somethings, i.e. www.yahoo.com
	 * @param theURL
	 * @return
	 */
	private boolean validateURL(final URL theURL) {
		boolean valid = false;
		String path = theURL.toString();
//		if (path.endsWith(".html") || !path.endsWith(".txt") || path.endsWith(".com") || !path.endsWith(".png")) {
		if (!path.endsWith(".txt") && !path.endsWith(".png") && !path.endsWith(".jpg") && !path.endsWith(".php") && !path.endsWith(".asp")) {
			valid = true;
		}
		return valid;		
	}
	
	public boolean queueNotEmpty() {
		boolean notEmpty = false;
		if (!myPagesToVisit.isEmpty()) {
			notEmpty = true;
		}
		return notEmpty;
	}
	public boolean getNextPage() {
		boolean pageInQueue = false;
		String currStringURL = new String();
//		System.out.println("I'm in the PR's getNextPage method");
		Page currPage = new Page();
		InputStream iStream = null;
		BufferedReader bReader;
		String myString = "";
		StringBuilder sBuilder = new StringBuilder();
		if (!myPagesToVisit.isEmpty()){
			try {
				URL temp = myPagesToVisit.remove(); //takes the head element off of queue
				currStringURL = temp.toString();
//				myVisitedPages.add(currStringURL); //already added in addPage method
				iStream = temp.openStream();
				bReader = new BufferedReader(new InputStreamReader(iStream));
				while ((myString = bReader.readLine()) != null) {
//					System.out.println(myString);
					sBuilder.append(myString);
				}
				currPage.buildRetrievedPage(temp.toString(), sBuilder.toString());
				this.setChanged();
//				this.notifyObservers(sBuilder.toString());
				this.notifyObservers(currPage);
				pageInQueue = true;
			} catch (IOException e) {
				System.out.println("'" + currStringURL + "' is not a valid URL!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
			}
		}
		if (myPagesToVisit.isEmpty()) {
			setChanged();
			notifyObservers("DONE");
		}
		return pageInQueue;
		//TODO: figure out if next line is necessary
//		return sBuilder.toString();
	}
	
	public void setUp(final int numPages) {
		totalPages = numPages;
	}
	
//	public static void main(final String args[]) throws MalformedURLException {
//		PageRetriever myPR = new PageRetriever();
//		myPR.addPage(new URL("http://css.insttech.washington.edu/~mealden/"));
//		System.out.println(myPR.getNextPage());
//	}	
}